package com.meichis.mcsappframework.encrypt;

import android.util.Base64;

import java.math.BigInteger;
import java.security.*;
import java.security.interfaces.RSAPrivateKey;
import java.security.interfaces.RSAPublicKey;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.spec.RSAPublicKeySpec;

import javax.crypto.Cipher;

public class RSAProvider {

	public static class RSAKeys {
		public static String RSAPrivateKey;// 私钥
		public static String Modulus;// 模
		public static String Exponent;// 公钥

	}

	public static void initKey() throws Exception {
		// 实例化密钥生成器
		KeyPairGenerator keypairgenerator = KeyPairGenerator.getInstance("RSA");
		// 初始化
		keypairgenerator.initialize(1024);
		// 获得密钥对
		KeyPair keypair = keypairgenerator.generateKeyPair();
		// 密钥
		RSAPrivateKey pritekey = (RSAPrivateKey) keypair.getPrivate();
		// 公钥
		RSAPublicKey pubkey = (RSAPublicKey) keypair.getPublic();

		// 将公钥和模进行Base64编码
		KeyFactory keyFactory = KeyFactory.getInstance("RSA");
		RSAPublicKeySpec publicSpec = keyFactory.getKeySpec(pubkey, RSAPublicKeySpec.class);
		BigInteger modulus = publicSpec.getModulus();
		BigInteger exponent = publicSpec.getPublicExponent();
		byte[] ary_m = modulus.toByteArray();// 注意：对公钥和模进行Base64编码时，不是对BigInteger对应的字符串编码，而是对其内部
		// 的字节数组进行编码
		byte[] ary_e = exponent.toByteArray();
		String str_m;
		String str_e;
		if (ary_m[0] == 0 && ary_m.length == 129)// 判断数组首元素是否为0，若是，则将其删除，保证模的位数是128
		{
			byte[] temp = new byte[ary_m.length - 1];
			for (int i = 1; i < ary_m.length; i++) {
				temp[i - 1] = ary_m[i];
			}
			str_m = Base64.encodeToString(temp, Base64.DEFAULT);
		} else {
			str_m = Base64.encodeToString(ary_m, Base64.DEFAULT);
		}

		str_e = Base64.encodeToString(ary_e, Base64.DEFAULT);

		RSAKeys.RSAPrivateKey = Base64.encodeToString(pritekey.getEncoded(), Base64.DEFAULT);
		RSAKeys.Exponent = str_e.replace("\n", "");
		RSAKeys.Modulus = str_m;

	}

	public static PublicKey getPublicKey(String modulus, String publicExponent) throws Exception {

		byte[] ary_exponent = Base64.decode(publicExponent, Base64.DEFAULT);
		byte[] ary_modulus = Base64.decode(modulus, Base64.DEFAULT);
		// 注意构造函数，调用时指明正负值，1代表正值，否则报错
		BigInteger big_exponent = new BigInteger(1, ary_exponent);
		BigInteger big_modulus = new BigInteger(1, ary_modulus);

		RSAPublicKeySpec keyspec = new RSAPublicKeySpec(big_modulus, big_exponent);
		KeyFactory keyfac = KeyFactory.getInstance("RSA");
		PublicKey publicKey = keyfac.generatePublic(keyspec);
		return publicKey;

	}

	public static PrivateKey getPrivateKey(String key) throws Exception {
		byte[] keyBytes = Base64.decode(key, Base64.DEFAULT);
		PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(keyBytes);
		KeyFactory keyFactory = KeyFactory.getInstance("RSA");
		PrivateKey privateKey = keyFactory.generatePrivate(keySpec);
		return privateKey;
	}

	// 公钥加密
	public static String encryptByPublicKey(PublicKey key, String data) throws Exception {
		Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");
		cipher.init(Cipher.ENCRYPT_MODE, key);
		return Base64.encodeToString(cipher.doFinal(data.getBytes("utf-8")), Base64.DEFAULT);
	}

	// 私钥解密
	public static String decryptByPrivateKey(PrivateKey key, String data) throws Exception {
		Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding");
		cipher.init(Cipher.DECRYPT_MODE, key);
		return new String(cipher.doFinal(Base64.decode(data.getBytes(), Base64.DEFAULT)), "UTF-8");
	}


}
